package com.gitee.wsl.security.encrypt.sample

import com.gitee.wsl.ext.string.stripAllSpace
import com.gitee.wsl.security.encrypt.Encrypt
import com.gitee.wsl.security.encrypt.StringToStringEncrypt
import com.gitee.wsl.security.encrypt.sample.PolybiusSquareCipher.Companion.DEFAULT_POLYBIUS_ENCODE_MAP

/** like polybius @link https://ctf-wiki.org/crypto/classical/polyalphabetic/#nihilist */

class NihilistCipher(val keyword: String,
                     val encodeMap: String = DEFAULT_POLYBIUS_ENCODE_MAP,
                     val replacePair: Pair<String, String> = "J" to "I") : StringToStringEncrypt {
   private val polybiusSquareCipher:PolybiusSquareCipher

    init {
        val maps = TABLE_A_Z_WO_J.toMutableList()
        keyword.stripAllSpace().uppercase().asIterable().distinct().also {
            maps.removeAll(it.toSet())
            maps.addAll(0, it)
        }
        polybiusSquareCipher= PolybiusSquareCipher(maps.joinToString(""), encodeMap,replacePair)
    }

    override fun decrypt(src: String): String {
        return polybiusSquareCipher.decrypt(src)
    }

    override fun encrypt(src: String): String {
        return polybiusSquareCipher.encrypt(src)
    }

}

const val TABLE_HANDY_CODE =
    "2 22 222 3 33 333 4 44 444 5 55 555 6 66 666 7 77 777 7777 8 88 888 9 99 999 9999"
const val TABLE_VOWEL = "1 11 12 13 2 21 22 23 3 31 32 33 34 35 4 41 42 43 44 45 5 51 52 53 54 55"
const val TABLE_A_Z = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
const val TABLE_A_Z_LOWER = "abcdefghijklmnopqrstuvwxyz"
const val TABLE_A_Z_WO_J = "ABCDEFGHIKLMNOPQRSTUVWXYZ"
const val TABLE_A_Z_WO_K = "ABCDEFGHIJLMNOPQRSTUVWXYZ"

fun Encrypt.Companion.nihilist(keyword: String,encodeMap: String = DEFAULT_POLYBIUS_ENCODE_MAP) = NihilistCipher(keyword, encodeMap)